// 版权所有2010 Go作者。保留所有权利。
// 此源代码的使用受BSD样式
// 许可证的约束，该许可证可以在许可证文件中找到。

package cmplx

import "math"

// 下面的原始C代码、长注释和常量
// 来自http:
// go代码是原始C.
// 
// Cephes数学库发行版2.8:2000年6月
// 版权所有1984、1987、1989、1992、2000作者Stephen L.Moshier 
// 
// http:
// 本档案中的一些软件可能来自《数学函数的方法和程序》（Prentice Hall或Simon&Schuster 
// International，1989）一书，也可能来自Cephes数学图书馆，一本
// 商业产品。无论哪种情况，它都是作者的版权。
// 您在这里看到的内容可以免费使用，但不提供任何支持或保证。
// 
// 本书中两个已知的印刷错误在这里的
// 伽马函数和不完整的beta 
// 积分的源代码列表中修复。
// 
// Stephen L.Moshier 
// moshier@na-网。奥尔。gov 

// 复数幂函数
// 
// 说明：
// 
// 将复数A提升为复数Zth幂。
// 定义符合AMS55#4.2.8，
// 在分析上等同于cpow（a，z）=cexp（z clog（a））。
// 
// 精度：
// 
// 相对误差：
// 算术域#试验峰值均方根
// IEEE-10，+10 30000 9.4e-15 1.5e-15 

// Pow返回x**y，y的基x指数。
// 用于与数学的广义兼容。Pow:
// Pow（0，±0）返回1+0i 
// Pow（0，c）为实（c）<0如果imag（c）为零，则返回Inf+0i，否则返回Inf+Inf i。
func Pow(x, y complex128) complex128 {
	if x == 0 { // x=-0也保证为真。
		if IsNaN(y) {
			return NaN()
		}
		r, i := real(y), imag(y)
		switch {
		case r == 0:
			return 1
		case r < 0:
			if i == 0 {
				return complex(math.Inf(1), 0)
			}
			return Inf()
		case r > 0:
			return 0
		}
		panic("not reached")
	}
	modulus := Abs(x)
	if modulus == 0 {
		return complex(0, 0)
	}
	r := math.Pow(modulus, real(y))
	arg := Phase(x)
	theta := real(y) * arg
	if imag(y) != 0 {
		r *= math.Exp(-imag(y) * arg)
		theta += imag(y) * math.Log(modulus)
	}
	s, c := math.Sincos(theta)
	return complex(r*c, r*s)
}
